﻿using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
using Reuse.PCL.Services;
using Reuse.WS81.Common;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using Windows.Storage;
using Windows.UI.Xaml.Controls;

namespace Reuse.WS.Services {
	public class StateService : IStateService{

		//public StateService() {
		//	Windows.UI.Xaml.Application.Current.Suspending += Current_Suspending;

		//}

		//async void Current_Suspending( object sender, Windows.ApplicationModel.SuspendingEventArgs e ) {
		//	await SuspensionManager.SaveAsync();
		//}

		public void RegisterAppFrame(object frame) {
			SuspensionManager.RegisterFrame((Windows.UI.Xaml.Controls.Frame)frame, "appFrame");
		}

		public async Task RestoreState() {
			await SuspensionManager.RestoreAsync();
			//await SuspensionManager.RestoreRoamingAsync();
		}

		public async Task SaveState() {
			await SuspensionManager.SaveAsync();
			//await SuspensionManager.SaveAsyncRoaming();
		}


        //public T GetState<T>( string key, bool isPersistentStorage = false )
        //{
        //    if ( !isPersistentStorage )
        //    {
        //        if ( ApplicationData.Current.LocalSettings.Values.ContainsKey( key ) )
        //        {
        //            var localSettings = ApplicationData.Current.LocalSettings;
        //            return Deserialize<T>(localSettings.Values[ key ].ToString( ));
        //        }
        //        else
        //        {
        //            return default( T );
        //        }
        //    }
        //    else
        //    {
        //        if ( ApplicationData.Current.RoamingSettings.Values.ContainsKey( key ) )
        //        {
        //            var roamingSettings = ApplicationData.Current.RoamingSettings;
        //            return Deserialize<T>( roamingSettings.Values[ key ].ToString( ) );
        //        }
        //        else
        //        {
        //            return default( T );
        //        }
        //    }
        //}

        public T GetState<T>( string key, bool isPersistentStorage = false )
        {
            //Task.Factory.StartNew( async () => SuspensionManager.RestoreAsync().Wait() ).Wait();

            if ( isPersistentStorage == false )
            {
                if ( SuspensionManager.SessionState.ContainsKey( key ) )
                {
                    var obj = SuspensionManager.SessionState[ key ];
                    //if ( obj is JArray ) {
                    //	return SuspensionManager.Deserialize<T>( ( (JArray)obj ).ToString() );
                    //} else if ( obj is JObject ) {
                    //	return SuspensionManager.Deserialize<T>( ( (JObject)obj ).ToString() );
                    //} else {
                    return ( T )obj;
                    //}
                }
                else
                {
                    return default( T );
                }
            }
            else
            {
                Windows.Storage.ApplicationDataContainer localSettings = Windows.Storage.ApplicationData.Current.LocalSettings;
              
                if ( localSettings.Values.ContainsKey( key ) )
                {
                    var obj = localSettings.Values[ key ];
                    //Windows.Storage.ApplicationDataContainer roamingSettings = Windows.Storage.ApplicationData.Current.RoamingSettings;
                    //if ( roamingSettings.Values.ContainsKey( key ) ) {
                    //	var obj = roamingSettings.Values[key];
                    //if ( obj is JArray ) {
                    //	return SuspensionManager.Deserialize<T>( ( (JArray)obj ).ToString() );
                    //} else if ( obj is JObject ) {
                    //	return SuspensionManager.Deserialize<T>( ( (JObject)obj ).ToString() );
                    //} else {
                    return Deserialize<T>(obj as string);
                    //}
                }
                else
                {
                    return default( T );
                }
            }
        }

        //public void SetState( string key, object value, bool isPersistentStorage = false )
        //{
        //    if ( !isPersistentStorage )
        //    {
        //        var localSettings = ApplicationData.Current.LocalSettings;
        //        localSettings.Values[ key ] = Serialize(value);
        //    }
        //    else
        //    {
        //        var roamingSettings = ApplicationData.Current.RoamingSettings;
        //        roamingSettings.Values[ key ] = Serialize( value );
        //    }
        //}

        public async void SetState( string key, object value, bool isPersistentStorage = false )
        {
            if ( isPersistentStorage == false )
            {
                if ( SuspensionManager.SessionState.ContainsKey( key ) )
                {
                    SuspensionManager.SessionState[ key ] = value ;
                }
                else
                {
                    SuspensionManager.SessionState.Add( key, value );
                }
                //await SuspensionManager.SaveAsync();
            }
            else
            {
                Windows.Storage.ApplicationDataContainer localSettings = Windows.Storage.ApplicationData.Current.LocalSettings;
                localSettings.Values[ key ] = Serialize(value);
                //await SuspensionManager.SaveAsync();


                //Windows.Storage.ApplicationDataContainer roamingSettings = Windows.Storage.ApplicationData.Current.RoamingSettings;
                //roamingSettings.Values[key] = SuspensionManager.Serialize( value );
            }
            //Task.Factory.StartNew( async () => SuspensionManager.SaveAsync().Wait() ).Wait();
        }



		public Dictionary<string, object> SessionStateForFrame(object frame) {
			return SuspensionManager.SessionStateForFrame( (Frame)frame );
		}

        private static T Deserialize<T>( string jsonString )
        {
            return JsonConvert.DeserializeObject<T>( jsonString );
        }
        private static string Serialize( object objectToSerialize )
        {
            return JsonConvert.SerializeObject( objectToSerialize, Formatting.None );
        }
	}
}
